﻿import mx.transitions.easing.Regular;
import mx.transitions.Tween;
import mx.utils.Delegate;
import com.dmotiko.util.*

class MovieEffects {
	
	public static function initEffects(argObject){
		if(argObject.rewind != false) MovieEffects.rewind();
		if(argObject.interpolate != false) MovieEffects.interpolate();
		if(argObject.fadeIn != false) MovieEffects.fadeIn();
		if(argObject.fadeOut != false) MovieEffects.fadeOut();
		if(argObject.delayFunction != false) MovieEffects.delayFunction();
		if(argObject.timer != false) MovieEffects.timer();
		if(argObject.watchTimeLine != false) MovieEffects.watchTimeLine();
	}
	
	public static function forward(){
		if(MovieClip.prototype.forward) return;
		MovieClip.prototype.forward = function(argObject:Object){
			var clip = this;
			var bindTo = argObject.bind;
			var nEnd = argObject.end ? argObject.end : clip._totalframes;
			var rate = argObject.rate ? argObject.rate : 1;
			var fListener = argObject.listener;
			var controller:MovieClip = DummyFactory.getNextDummy(clip);
		
			controller.onEnterFrame = function(){
				if(clip._currentframe == nEnd){
					delete this.onEnterFrame;
					if(bindTo) Delegate.create(bindTo, fListener)(clip);
					else fListener(clip);
					this.removeMovieClip();
					
				} else {
					for (var i:Number = 0; i < rate; i++) {
						clip.nextFrame();	
					}
				}
			}
			
			controller.stopEffect = function(){
				delete this.onEnterFrame;
				this.removeMovieClip();
			}
			
			return controller;
		}
	}
	
	public static function rewind(){
		if(MovieClip.prototype.rewind) return;
		MovieClip.prototype.rewind = function(argObject:Object){
			var clip = this;
			var bindTo = argObject.bind;
			var nEnd = argObject.end ? argObject.end : 1;
			var rate = argObject.rate ? argObject.rate : 1;
			var fListener = argObject.listener;
			var controller:MovieClip = DummyFactory.getNextDummy(clip);
		
			controller.onEnterFrame = function(){
				if(clip._currentframe == nEnd){
					delete this.onEnterFrame;
					if(bindTo) Delegate.create(bindTo, fListener)(clip);
					else fListener(clip);
					this.removeMovieClip();
					
				} else {
					for (var i:Number = 0; i < rate; i++) {
						clip.prevFrame();	
					}					
				}
			}
			
			controller.stopEffect = function(){
				delete this.onEnterFrame;
				this.removeMovieClip();
			}
			
			return controller;
		}
	}
	public static function interpolate(){
		if(MovieClip.prototype.interpolate) return;
		MovieClip.prototype.interpolate = function(argObject:Object){
			var clip = this;
			var prop = argObject.prop;
			var nInit = argObject.init;
			var nEnd = argObject.end;
			var nRatio = argObject.ratio ? argObject.ratio : 3;
			var bindTo = argObject.bind;
			var fListener = argObject.listener;
			var root = argObject.root;
			var controller = new Object();
			
			var tween:Tween = new Tween(this, prop, Regular.easeOut, nInit, nEnd, 0.2 * nRatio, true);
			var oListener:Object = new Object();
			oListener.onMotionFinished = function() {
				if ( bindTo ) Delegate.create(bindTo, fListener)(clip);
				else fListener(clip);
			}
			tween.addListener( oListener );
						
			controller.stopEffect = function(){
				tween.stop();
				delete tween;
			}
			
			return controller;
		}
	}
	
	public static function fadeIn(){
		if(MovieClip.prototype.fadeIn) return;
		MovieClip.prototype.fadeIn = function(argObject:Object){
			if ( this.tween ) this.tween.stop();
						
			var fade = new Object();
			var bindTo = argObject.bind;
			var fListener = argObject.listener;
			var rate = argObject.rate ? argObject.rate : 3;
			var clip = this;
			var tween:Tween = new Tween( this, "_alpha", Regular.easeOut, this._alpha, 100, 0.2*rate,true);
			var oListener:Object = new Object();
			oListener.onMotionFinished = function() {
				if ( bindTo ) Delegate.create(bindTo, fListener)(clip);
				else fListener(clip);
			}
			tween.addListener( oListener );
			fade.remove = function(){
				tween.stop();
				delete tween;
			}
			return fade;
		}
	}
	public static function fadeOut(){
		if(MovieClip.prototype.fadeOut) return;
		MovieClip.prototype.fadeOut = function(argObject:Object){
			if ( this.tween ) this.tween.stop();
						
			var fade = new Object();
			var bindTo = argObject.bind;
			var fListener = argObject.listener;
			var rate = argObject.rate ? argObject.rate : 3;
			var clip = this;
			var tween:Tween = new Tween( this, "_alpha", Regular.easeOut, this._alpha, 0, 0.2*rate,true);
			var oListener:Object = new Object();
			oListener.onMotionFinished = function() {
				if ( bindTo ) Delegate.create(bindTo, fListener)(clip);
				else fListener(clip);
			}
			tween.addListener( oListener );
			fade.remove = function(){
				tween.stop();
				delete tween;
			}
			return fade;
		}
	}
	public static function delayFunction(){
		if(MovieClip.prototype.delayFunction) return;
		MovieClip.prototype.delayFunction = function(argObject){
			var clip = this;
			var delay = this.createEmptyMovieClip("delay", this.getNextHighestDepth());
			var nDelay = argObject.delay;
			var data = argObject.data;
			var bindTo = argObject.bind;
			var fListener = argObject.listener;
			var nTimer = getTimer();
			
			delay.onEnterFrame = function(){
				if(getTimer() - nTimer > nDelay){
					delete this.onEnterFrame;
					this.removeMovieClip();
					if(bindTo) Delegate.create(bindTo, fListener)(clip, data);
					else fListener(clip, data);
				}
			}
			delay.remove = function(){
				delete this.onEnterFrame;
				this.removeMovieClip();
			}
			return delay;
		}
	}
	
	public static function timer(){
		if(MovieClip.prototype.timer) return;
		MovieClip.prototype.timer = function(argObject){
			var clip = this;
			var controller:MovieClip = DummyFactory.getNextDummy(clip);
			var nFrames = argObject.frames;
			var bindTo = argObject.bind;
			var fListener = argObject.listener;
			
			var nTimer:Number = getTimer();
			var nCount:Number = 0;
			
			controller.onEnterFrame = function(){
				if(nCount > nFrames){
					delete this.onEnterFrame;
					if(bindTo) Delegate.create(bindTo, fListener)(clip);
					else fListener(clip);
					this.removeMovieClip();
					
				} else {
					nCount++;
				}
			}
			
			controller.stopEffect = function(){
				delete this.onEnterFrame;
				this.removeMovieClip();
			}
			
			return controller;
		}
	}
	
	public static function watchTimeLine(){
		if(MovieClip.prototype.watchTimeLine) return;
		MovieClip.prototype.watchTimeLine = function(argObject){
			var clip = this;
			var percent = argObject.percent;
			var bindTo = argObject.bind;
			var fListener = argObject.listener;
			
			var controller = DummyFactory.getNextDummy(clip);
			
			var total:Number = clip._totalframes;
			var nFrame:Number = percent * total / 100;
			
			controller.onEnterFrame = function(){
				if(clip._currentframe >= nFrame){
					delete this.onEnterFrame;
					
					if(bindTo) Delegate.create(bindTo, fListener)(clip, percent);
					else fListener(clip, percent);
					this.removeMovieClip();
				}
			}
			
			controller.stopWatcher = function(){
				delete this.onEnterFrame;
				this.removeMovieClip();
			}
			
			return controller;
		}
	}
	
}